package com.crane.oss.school.syn;


import com.crane.common.core.dto.Response;
import com.crane.common.core.utils.CollectionUtil;
import com.crane.common.core.utils.StringUtil;
import com.crane.common.framework.utils.Jackson2JsonUtil;
import com.crane.oss.api.bean.resp.SchoolResp;
import com.crane.oss.api.constants.SynchronousRedisQueue;
import com.crane.oss.sports.XunFeiPushEventApiService;
import com.crane.oss.sports.bean.resquest.SynRedisDataReq;
import com.crane.oss.sys.service.impl.RoleServiceImpl;
import com.crane.oss.xunfei.req.UpdateEventReq;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.data.redis.core.RedisCallback;
import org.springframework.data.redis.core.RedisTemplate;
import org.springframework.stereotype.Component;

import javax.annotation.Resource;
import java.util.ArrayList;
import java.util.List;
import java.util.Map;
import java.util.stream.Collectors;

@Component
public class SynXunfeiService {

    private static final Logger logger = LoggerFactory.getLogger(SynXunfeiService.class);

    @Resource
    RedisTemplate redisTemplate;

    @Resource
    XunFeiPushEventApiService xunFeiPushEventApiService;

    public <T> Response pushDate(T data, String eventType, String opType, String schoolId, String opUserId) {
        SynRedisDataReq<T> request = new SynRedisDataReq<>();
        String queue = "";
        if (eventType.equals(XunFeiPushEventApiService.EVENT_CAMPUS)) {
            if (opType.equals(XunFeiPushEventApiService.INSERT)) {
                queue = SynchronousRedisQueue.AREA_QUEUE_ADD;
            } else if (opType.equals(XunFeiPushEventApiService.UPDATE)) {
                queue = SynchronousRedisQueue.AREA_QUEUE_UPDATE;
            } else if (opType.equals(XunFeiPushEventApiService.DELETE)) {
                queue = SynchronousRedisQueue.AREA_QUEUE_DELETE;
            }
        } else if (eventType.equals(XunFeiPushEventApiService.EVENT_GRADE_CLASS)) {
            if (opType.equals(XunFeiPushEventApiService.INSERT)) {
                queue = SynchronousRedisQueue.CLASS_QUEUE_ADD;
            } else if (opType.equals(XunFeiPushEventApiService.UPDATE)) {
                queue = SynchronousRedisQueue.CLASS_QUEUE_UPDATE;
            } else if (opType.equals(XunFeiPushEventApiService.DELETE)) {
                queue = SynchronousRedisQueue.CLASS_QUEUE_DELETE;
            }
        } else if (eventType.equals(XunFeiPushEventApiService.EVENT_STUDENT)) {
            if (opType.equals(XunFeiPushEventApiService.INSERT)) {
                queue = SynchronousRedisQueue.STUDENT_QUEUE_ADD;
            } else if (opType.equals(XunFeiPushEventApiService.UPDATE)) {
                queue = SynchronousRedisQueue.STUDENT_QUEUE_UPDATE;
            } else if (opType.equals(XunFeiPushEventApiService.DELETE)) {
                queue = SynchronousRedisQueue.STUDENT_QUEUE_DELETE;
            }
        } else if (eventType.equals(XunFeiPushEventApiService.EVENT_TEACHER)) {
            if (opType.equals(XunFeiPushEventApiService.INSERT)) {
                queue = SynchronousRedisQueue.TEACHER_QUEUE_ADD;
            } else if (opType.equals(XunFeiPushEventApiService.UPDATE)) {
                queue = SynchronousRedisQueue.TEACHER_QUEUE_UPDATE;
            } else if (opType.equals(XunFeiPushEventApiService.DELETE)) {
                queue = SynchronousRedisQueue.TEACHER_QUEUE_DELETE;
            }
        } else if (eventType.equals(XunFeiPushEventApiService.EVENT_REF_STUDENT_CLASS)) {
            if (opType.equals(XunFeiPushEventApiService.INSERT)) {
                queue = SynchronousRedisQueue.REF_CLASS_QUEUE_ADD;
            } else if (opType.equals(XunFeiPushEventApiService.UPDATE)) {
                queue = SynchronousRedisQueue.REF_CLASS_QUEUE_UPDATE;
            } else if (opType.equals(XunFeiPushEventApiService.DELETE)) {
                queue = SynchronousRedisQueue.REF_CLASS_QUEUE_DELETE;
            }
        } else if (eventType.equals(XunFeiPushEventApiService.EVENT_TEACH_CYCLE)) {
            if (opType.equals(XunFeiPushEventApiService.INSERT)) {
                queue = SynchronousRedisQueue.TEACHCYCLE_QUEUE_ADD;
            } else if (opType.equals(XunFeiPushEventApiService.UPDATE)) {
                queue = SynchronousRedisQueue.TEACHCYCLE_QUEUE_UPDATE;
            } else if (opType.equals(XunFeiPushEventApiService.DELETE)) {
                queue = SynchronousRedisQueue.TEACHCYCLE_QUEUE_DELETE;
            }
        }

        if (StringUtil.isEmpty(queue)) {
            return Response.buildFailure("错误的类型");
        }
        request.setEvent(eventType);
        request.setOperate(opType);
        request.setSchoolId(schoolId);
        request.setOpUserId(opUserId);
        request.setData(data);
        logger.info("pushDate req={}",Jackson2JsonUtil.toString(request));
        redisTemplate.opsForList().rightPush(queue, request);
        return Response.buildSuccess();
    }

    public Response sysData(String queue) {
        int size = 100;
        List<List<SynRedisDataReq>> redisResult = redisTemplate.executePipelined(
                (RedisCallback<SynRedisDataReq>) redisConnection -> {
                    redisConnection.openPipeline();
                    redisConnection.lRange(redisTemplate.getKeySerializer().serialize(queue), 0, size);
                    redisConnection.lTrim(redisTemplate.getKeySerializer().serialize(queue), size, -1);
                    return null;
                }, redisTemplate.getValueSerializer());
        if (CollectionUtil.isEmpty(redisResult.get(0))) {
            return Response.buildSuccess();
        }
        try {
            Map<String, List<SynRedisDataReq>> map = redisResult.get(0).stream().collect(Collectors.groupingBy(SynRedisDataReq::getSchoolId));
            map.forEach((key, value) -> {
                SynRedisDataReq synRedisDataReq = value.get(0);
                UpdateEventReq req = new UpdateEventReq();
                req.setSchoolId(key);
                req.setEvent(synRedisDataReq.getEvent());
                req.setOperate(synRedisDataReq.getOperate());
                List<Object> obj=new ArrayList<>();
                for(SynRedisDataReq synRedisDataReq1 : value){
                    obj.add(synRedisDataReq1.getData());
                }
                req.setBody(Jackson2JsonUtil.toString(obj));
                logger.info("sysData req={}",Jackson2JsonUtil.toString(req));
                xunFeiPushEventApiService.updateEvent(req, key, null, synRedisDataReq.getOpUserId());
            });
        }catch (Exception e){
            logger.error("sysData req={}",Jackson2JsonUtil.toString(redisResult));
            redisTemplate.opsForList().leftPushAll(queue,redisResult);
        }
        return Response.buildSuccess();
    }
}
